package com.example.jdktest.model;

import com.fasterxml.jackson.annotation.*;
import com.fasterxml.jackson.databind.annotation.JsonDeserialize;
import com.fasterxml.jackson.databind.annotation.JsonSerialize;
import lombok.Data;
import org.springframework.format.annotation.DateTimeFormat;

import java.io.Serializable;
import java.util.Date;

/**
 * @author: dangwen
 * @createDate: 2020/11/26
 */
//@JsonDeserialize
//@JsonSerialize

/**
 * // 输出结果时，去除value为null的键值对，作用于类
 * <例子：入参{"name":null，"age":18}，输出{"age":18}>
 *     也可以这么写：@JsonSerialize(include = JsonSerialize.Inclusion.NON_NULL)，不过Jackson 2.0后已经废弃了。
 *     as it said: @deprecated As of Jackson 2.0, this annotation has been replaced by {@link com.fasterxml.jackson.annotation.JsonInclude}
 */
@JsonInclude(JsonInclude.Include.NON_NULL)
@JsonIgnoreProperties(value = {"ignore1", "ignore2"}) // 忽略指定字段
@Data
public class JsonOrDateFormatTest implements Serializable {
//    @DateTimeFormat(pattern = "yyyy-MM-dd'T'HH:mm:ss.SSSX")
    //    @DateTimeFormat(pattern = "yyyy-MM-dd HH:mm:ss")
    /**
     * @JsonFormat 用于PostMapping。GetMapping无效，控制不了入参格式，只能控制出参格式。
     * <例子：入参：2020-11-27 12:20:02，代码中获取到：Fri Nov 27 00:00:00 CST 2020，出参：2020-11-27>
     * @DateTimeFormat 用于GetMapping。PostMapping无效。控制不了出参格式，需要配合@JsonFormat控制出参格式
     * <例子：入参：2020-11-27 12:20:02，代码中获取到：Fri Nov 27 00:00:00 CST 2020，出参：2020-11-26T16:00:00.000+00:00>
     *     综上：post请求，参数中带有时间入参的，一个@JsonFormat即可搞定。没有@DateTimeFormat也不会报错。
     *          get请求，参数中带有时间入参的，需要使用@DateTimeFormat接收转化时间字符串，还需要使用@JsonFormat控制出参格式。
     *
     *      如果一个model想要兼容post和get两种形式的入参是string类型的时间，需要把这两种注解都加上。（兼容get）
     */
    @DateTimeFormat(pattern = "yyyy-MM-dd")
    @JsonFormat(pattern = "yyyy-MM-dd", timezone = "GMT+8")
    private Date timestampJson;
    @JsonFormat(pattern = "yyyy-MM-dd", timezone = "GMT+8")
    @DateTimeFormat(pattern = "yyyy-MM-dd")
    private Date timestampDate;
    @JsonIgnore // 忽略字段为name的出入参
    private String name;
    @JsonProperty("test_age") // 出入参字段都变为了test_age，不能再使用age传值
    private int age;
    private String ignore1;
    private String ignore2;
    /**
     * 说明：
     * json相关注解和序列化与反序列化
     * 使用jackson进行序列化时，往往会遇到后台某个实体对象的属性为null，当序列化成json时对应的属性也为null，可以用以下的注解方式完成当属性为null时不参与序列化：
     * @JsonSerialize(include = JsonSerialize.Inclusion.NON_NULL)
     *
     * @JsonIgnoreProperties
     * 类注解，作用是json序列化时将bean中的一些属性忽略掉，序列化和反序列化都受影响。
     *
     * @JsonIgnore
     * 作用于属性或字段上，当生成json时忽略有该annotation的方法或字段。
     *
     * @JsonProperty("rename")
     * 作用于属性或字段上，对其重命名。
     *
     * @JsonFormat
     * 作用于属性或字段上，方便把Date类型直接转化为我们想要的模式，如@JsonFormat(pattern="yyyy-MM-dd HH-mm-ss")
     *
     * @JsonSerialize
     * 作用于属性或字段上，指定序列化方式。
     * 例如：@JsonSerialize(as=BasicType.class)将类型序列化成指定类型；@JsonSerialize(using=CustomDoubleSerialize.class)用于在序列化时嵌入我们自定义的代码，比如序列化一个double时在其后限制两位小数。
     *
     * @JsonDeserialize
     * 作用于属性或字段上，指定反序列化方式。
     * 例如：@JsonDeserialize(as=ValueImpl.class)将类型反序列化成指定类型；@JsonDeserialize(using=CustomDateDeserialize.class)用于在反序列化时嵌入我们自定义的代码。
     */
}
